<!--
* @author wn
* @date 2023/08/03 10:12:53
* @description: 猜你喜欢 通用组件
!-->
<template>
	<!-- 猜你喜欢 -->
	<text class="caption">猜你喜欢</text>
	<view class="guess">
		<NavigatorGoods v-for="good in guessList" :key="good.id" :good="good" />
	</view>
	<view class="loading-text">
		{{ isLoading ? '正在加载...' : '没有更多数据~' }}
	</view>
</template>
<script lang="ts" setup>
import { getHomeGuessLikeApi } from '@/api/home'
import { reactive, ref, watch, onMounted } from 'vue'

// 分页参数
const pageParams = reactive<Required<PageParams>>({
	page: 0,
	pageSize: 10,
})

// 猜你喜欢的列表
const guessList = ref<GoodItem[]>([])

// 是否加载中  防止多次请求
const isLoading = ref(false)
// 已结束标记
const isFinish = ref(false)

/**
 * watch pageParams 获取猜你喜欢数据
 * v-if 导致 setup 执行了两次  v-show 不会 onMounted中也不会
 */
onMounted(() => (pageParams.page = 1))

watch(pageParams, async newValue => {
	// 如果数据出于加载中，退出函数
	if (isLoading.value) return
	// 发送请求前，标记为加载中
	isLoading.value = true
	// 调用 API 获取数据
	const { pages, items } = await getHomeGuessLikeApi(newValue)
	// 数组追加
	guessList.value.push(...items)
	// 参数的页数 >= pages 已结束
	newValue.page >= pages && (isFinish.value = true)
	// 发送请求后，重置标记
	isLoading.value = false
})

// 上拉加载更多
const getMore = () => {
	// 已经结束  不触发 watch
	if (isFinish.value)
		return uni.showToast({ icon: 'none', title: '没有更多数据~' })
	pageParams.page++
}

// 下拉刷新--重置数据
const resetData = () => {
	guessList.value = []
	isFinish.value = false
	if (pageParams.page === 1) {
		pageParams.page = 0
		pageParams.page = 1
	} else {
		pageParams.page = 1
	}
}

// 组件调用 暴露出去
defineExpose({
	getMore,
	resetData,
})
</script>
<style lang="scss">
/* 分类标题 */
.caption {
	display: flex;
	justify-content: center;
	align-items: center;
	font-size: 32rpx;
	color: #262626;
	padding: 36rpx 0;
	&::before,
	&::after {
		content: '';
		width: 20rpx;
		height: 20rpx;
		background: url('@/static/images/bubble.png') center/contain;
		margin: 0 10rpx;
	}
}

/* 猜你喜欢 */
.guess {
	display: flex;
	flex-wrap: wrap;
	justify-content: space-between;
	margin: 0 20rpx;
}
// 加载提示文字
.loading-text {
	text-align: center;
	font-size: 28rpx;
	color: #666;
	padding: 20rpx 0;
}
</style>
